package deng.java.examples;

// See http://www.redhat.com/docs/manuals/jboss/jboss-eap-4.2/doc/Server_Configuration_Guide/Using_JMX_as_a_Microkernel-Writing_JBoss_MBean_Services.html
// Needs META-INF/jboss-service.xml to deploy.
//
// The JNDIMap MBean implementation - Similiar to JNDIMap, but use a JBoss specific support class.
// - We don't have to mange start flag.
// - It provided a log object!
// - The jboss-service may use the <depends> tag!
//
import java.util.HashMap;
import javax.naming.InitialContext;
import javax.naming.Name;
import javax.naming.NamingException;
import org.jboss.naming.NonSerializableFactory;

public class JNDIMap2 extends org.jboss.system.ServiceMBeanSupport implements JNDIMap2MBean
{	
    private String jndiName;
    private HashMap contextMap = new HashMap();
    	
    public String getJndiName()
    {
        return jndiName;
    }

    public void setJndiName(String jndiName) throws NamingException
    {
		String oldName = this.jndiName;
        this.jndiName = jndiName;
		log.trace("Old jndiName=" + oldName);
        if (super.getState() == STARTED) {
            unbind(oldName);
            try {
                rebind();
            } catch(Exception e) {
                NamingException ne = new NamingException("Failed to update jndiName=" + jndiName);
                ne.setRootCause(e);
                throw ne;
            }
        }
    }
    
	// We are using startService instead of start.
    public void startService() throws Exception
    {
		log.trace("Starting service.");		
        rebind();
		log.debug("Service is ready");
    }

    public void stopService()
    {
		log.trace("Stopping service.");
        unbind(jndiName);
		log.debug("Service destroyed.");
    }
    
    private void rebind() throws NamingException
    {
        InitialContext rootCtx = new InitialContext();
        Name fullName = rootCtx.getNameParser("").parse(jndiName);
        log.info("fullName="+fullName);
        NonSerializableFactory.rebind(fullName, contextMap, true);
    }

    private void unbind(String jndiName)
    {
        try {
            InitialContext rootCtx = new InitialContext();
            rootCtx.unbind(jndiName);
            NonSerializableFactory.unbind(jndiName);
        } catch(NamingException e) {
            log.error("Failed to unbind map", e);
        }
    }
}
